package pe.bf.extranet.web;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.math.BigDecimal;
import java.math.BigInteger;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.Iterator;
import java.util.List;
import java.util.StringTokenizer;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.fileupload.FileItem;
import org.apache.commons.fileupload.FileItemFactory;
import org.apache.commons.fileupload.FileUploadException;
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
import org.apache.commons.fileupload.servlet.ServletFileUpload;
import org.apache.poi.hssf.usermodel.HSSFCell;
import org.apache.poi.hssf.usermodel.HSSFRow;
import org.apache.poi.hssf.usermodel.HSSFSheet;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.poifs.filesystem.POIFSFileSystem;

import pe.bf.domain.bean.Abono;
import pe.bf.domain.bean.Adjunto;
import pe.bf.domain.bean.Empleado;
import pe.bf.domain.bean.Moneda;
import pe.bf.domain.bean.SolicitudAbono;
import pe.bf.domain.bean.SolicitudCreacion;
import pe.bf.domain.bean.TipoCuenta;
import pe.bf.domain.bean.TipoDocumento;
import pe.bf.domain.bean.Transferencia;
import pe.bf.domain.bean.Usuario;
import pe.bf.extranet.cliente.ClienteWS;

/**
 * Servlet implementation class servlet
 */
public class SolAboCtaServlet extends HttpServlet {
	private static final long serialVersionUID = 1L;
       

    public SolAboCtaServlet() {
        super();
        // TODO Auto-generated constructor stub
    }


	protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		doPost(request, response);
	}

	public byte[] read(File file) throws IOException {
		 


	    byte []buffer = new byte[(int) file.length()];
	    InputStream ios = null;
	    try {
	        ios = new FileInputStream(file);
	        if ( ios.read(buffer) == -1 ) {
	            throw new IOException("EOF reached while trying to read the whole file");
	        }        
	    } finally { 
	        try {
	             if ( ios != null ) 
	                  ios.close();
	        } catch ( IOException e) {
	        }
	    }

	    return buffer;
	}
	
	

	private void obtenerListaTransferencias(HttpServletRequest request) {
		Usuario usuario=(Usuario)request.getSession().getAttribute("usuarioBean");
		Transferencia transferencia=new Transferencia();
		transferencia.setEmpresa(usuario.getEmpresa());
		transferencia.setEstado("UTILIZADA".toUpperCase());
		List<Transferencia> listaTransferencias= ClienteWS.listarTranferenciaPorEstado(transferencia);
		request.setAttribute("listaTransferencias", listaTransferencias);  
	}
	

	protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		Usuario usuario=(Usuario)request.getSession().getAttribute("usuarioBean");
		if(usuario==null){
            request.getRequestDispatcher("servlet").forward(request, response); 
            return;
		}
		String p_accion=request.getParameter("accion");
		obtenerListaTransferencias(request);
		obtenerMonedas(request);
		obtenerListaSolicitudes(request,usuario.getEmpresa().getIdEmpresa()); 
		obtenerTipoCuentas(request);
		String p_archivo=request.getParameter("txtArchivo");
		String p_descripcion=request.getParameter("txtDescripcion");
		String p_monto=request.getParameter("txtMonto");
		String p_moneda=request.getParameter("txtMoneda");
		String p_tipo=request.getParameter("txtTipoCuenta");
		String p_origen=request.getParameter("origenConcatenado"); 
 
		File uploadedFile = null;
		boolean isMultipart = ServletFileUpload.isMultipartContent(request);

	        if (isMultipart) {
	        	
	        	FileItemFactory factory = new DiskFileItemFactory();
	            ServletFileUpload upload = new ServletFileUpload(factory);
	            
	            try {
	                List items = upload.parseRequest(request);
	                Iterator iterator = items.iterator();
	                while (iterator.hasNext()) {
	                    FileItem item = (FileItem) iterator.next();  
	                        if(item.getFieldName().equals("accion")){
	                        	p_accion=item.getString();
	                        }else if(item.getFieldName().equals("txtDescripcion")){
	                        	p_descripcion=item.getString();
	                        }else if(item.getFieldName().equals("txtTipoCuenta")){
	                        	p_tipo=item.getString();
		                    }else if(item.getFieldName().equals("txtMonto")){
	                        	p_monto=item.getString();
		                    }else if(item.getFieldName().equals("origenConcatenado")){
		                    	p_origen=item.getString();
		                    }else if(item.getFieldName().equals("txtMoneda")){
		                    	p_moneda=item.getString();
		                    }else if(item.getFieldName().equals("txtArchivo") && !p_accion.equals("")  ){
	                      	  String root = getServletContext().getRealPath("/");
	                            File path = new File(root + "/solAboCtaServlet");
	                            if (!path.exists()) {
	                                boolean status = path.mkdirs();
	                            } 
	                            uploadedFile = new File(path + "/" + item.getName()); 
	                            item.write(uploadedFile);
	                        }           
	                }
	            } catch (FileUploadException e) {
	                e.printStackTrace();
	                request.setAttribute("error", "Error al abrir el archivo. Confirmar si el formato es correcto.");
	                request.getRequestDispatcher("solcreaabo.jsp").forward(request, response);
	                return;
	            } catch (Exception e) {
	                e.printStackTrace();
	                request.setAttribute("error", "Error al abrir el archivo. Confirmar si el formato es correcto.");
	                request.getRequestDispatcher("solcreaabo.jsp").forward(request, response);
	                return;
	            }
	            
	        	
	        }
	        
	        
	        
	        SimpleDateFormat formatoDelTexto = new SimpleDateFormat("ddMMyyyy");
		if(p_accion!=null){
			 if(p_accion.equals("grabar_abono_cuenta")){
				 SolicitudAbono solicitudabono=new SolicitudAbono();
				 solicitudabono.setNombrearchivo(uploadedFile.getName());
				 StringTokenizer descompuesto=new StringTokenizer(uploadedFile.getName(),"-");
				 Date fechaSolicitud=null;
				 try {
					 String ruc=descompuesto.nextToken();
					 String nroRegistros=descompuesto.nextToken();
					 String fechaSolicitudStr=descompuesto.nextToken();
					 fechaSolicitudStr=fechaSolicitudStr.substring(0,8);
					 System.out.println("parse " + fechaSolicitudStr );
					 fechaSolicitud = formatoDelTexto.parse(fechaSolicitudStr); 
					 solicitudabono.setFechacargaArchivo(fechaSolicitudStr);
					 
				} catch (Exception e) {
					  
					request.setAttribute("error", "Nombre de archivo no tiene el formato correcto RUC-NROREGISTROS-FECHA(DDMMYYYY).xls");
					e.printStackTrace();
					request.getRequestDispatcher("solabocta.jsp").forward(request, response); 
					return;
				}
				 
				 solicitudabono.setDescripcion(p_descripcion);
				 solicitudabono.setMontototal(new BigDecimal(p_monto));
				 solicitudabono.setTipoabono(p_tipo);
				 solicitudabono.setMoneda(p_moneda);
				 Adjunto adjunto=new Adjunto();
				 adjunto.setArchivo(read(uploadedFile));
				 solicitudabono.setAdjunto(adjunto);
				 List<Abono> listaAbono=new ArrayList();
				 double acumula_montos=0.0;
				 try
					{
					FileInputStream fileInputStream = new FileInputStream(uploadedFile); 
					POIFSFileSystem fsFileSystem = new POIFSFileSystem(fileInputStream); 
					HSSFWorkbook workBook = new HSSFWorkbook(fsFileSystem);
					HSSFSheet hssfSheet = workBook.getSheetAt(0); 
					Iterator rowIterator = hssfSheet.rowIterator();
					
					if(rowIterator.hasNext()){
						rowIterator.next();  	
					}
					 
					
						while (rowIterator.hasNext())
						{
								Abono abono=new Abono();
								HSSFRow hssfRow = (HSSFRow) rowIterator.next();
								Iterator iterator = hssfRow.cellIterator();  
								abono.setTipodocumento(getLong(iterator.next())+""); 
								abono.setMoneda(Long.valueOf(p_moneda)+"");  
								abono.setNrodocumento(getLong(iterator.next())+"");
								abono.setNrocuenta(getLong(iterator.next())+"");
								abono.setNombres(((HSSFCell) iterator.next()).getStringCellValue()); 
								abono.setMonto(new BigDecimal(((HSSFCell) iterator.next()).getNumericCellValue()));
								System.out.println("tipo " + abono.getTipodocumento());
								acumula_montos=acumula_montos+abono.getMonto().doubleValue();
								
								listaAbono.add(abono);
						}
					}
					catch (Exception e)
					{
						 
						request.setAttribute("error", "Error al leer celdas del archivo. Confirme si el formato es correcto");
						e.printStackTrace();
						request.getRequestDispatcher("solabocta.jsp").forward(request, response); 
						return;
					}
				 
				 solicitudabono.setEmpresa(usuario.getEmpresa());
				 solicitudabono.setNroempleados(new BigDecimal(listaAbono.size()));
				 solicitudabono.setTotalempleados(new BigDecimal(acumula_montos));
				 solicitudabono.setUsuariocreacion(usuario.getIdUsuario()+"");
				 solicitudabono.setAbonos(listaAbono);
				 
				 if(solicitudabono.getMontototal().compareTo(solicitudabono.getTotalempleados())!=0){
						request.setAttribute("error", "El monto de la solicitud de abono no coincide con el monto total de empleados."); 
						request.getRequestDispatcher("solabocta.jsp").forward(request, response); 
						return;
				 }
				 List<Transferencia> origenes=new ArrayList();
				 StringTokenizer listaOrigen=new StringTokenizer(p_origen,"-");
				 while(listaOrigen.hasMoreElements()){
					 Transferencia t =new Transferencia();
					 t.setIdTransferencia(Long.valueOf(listaOrigen.nextToken()));
					 origenes.add(t);
				 }
				 
				 solicitudabono.setTransferencias(origenes);
				 
				 System.out.println("transferencias " + origenes );
				 
				 List<String> resultado=grabarSolicitud(solicitudabono);
				 if(resultado!=null && resultado.size()==0){
					 request.setAttribute("mensaje", "Solicitud creada exitosamente.");
 				 }else{
					 request.setAttribute("error", "Error al intentar crear la solicitud.");
					 request.setAttribute("listaErrores",resultado);
				 }
				 
			 } else if(p_accion.equals("detalle")){
				 
				 String var_descripcion="";
				 List lista=new ArrayList();
				 request.setAttribute("cabeceraDetalle", var_descripcion);
				 request.setAttribute("listaDetalle", lista); 
			 }
			 obtenerListaTransferencias(request);
			 obtenerListaSolicitudes(request,usuario.getEmpresa().getIdEmpresa()); 
			 request.getRequestDispatcher("solabocta.jsp").forward(request, response);
			 return;
		}else{
			obtenerListaTransferencias(request);
			obtenerListaSolicitudes(request,usuario.getEmpresa().getIdEmpresa()); 
			request.getRequestDispatcher("solabocta.jsp").forward(request, response);
			return;
		}
		
		
	}

	
	

	private Long getLong(Object objecto)throws Exception{
		try{
		Long value=Long.valueOf((long)((HSSFCell) objecto ).getNumericCellValue());
		return value;
		}catch(Exception exception){
			throw new Exception("Verifique el o los numeros de cuenta.");
		}
		
	}
	
	
	private void obtenerMonedas(HttpServletRequest request) { 
		List<Moneda> lista=ClienteWS.findMonedas();
		request.setAttribute("lista_moneda", lista);// llamar a ws 
	}
	
	
	
	private void obtenerTipoCuentas(HttpServletRequest request) { 
		List<TipoCuenta> lista= ClienteWS.findTipoCuentas();
		request.setAttribute("lista_tipoCuenta", lista);// llamar a ws 
	}
	
 

	private void obtenerListaSolicitudes(HttpServletRequest request,long codigoEmpresa) {

		List<SolicitudAbono> lista= ClienteWS.listarSolicitudAbonoPorEmpresa(new BigInteger(codigoEmpresa+"")) ;
		request.setAttribute("listaSolicitudes", lista);// llamar a ws
		
	}

	private List<String> grabarSolicitud(SolicitudAbono solicitudabono) { 
		return ClienteWS.createSolicitudAbono(solicitudabono);
	}

}
